home *** CD-ROM | disk | FTP | other *** search
/ Usenet 1993 July / InfoMagic USENET CD-ROM July 1993.ISO / sources / misc / volume7 / cal < prev    next >
Encoding:
Text File  |  1989-08-05  |  7.4 KB  |  322 lines

  1. Newsgroups: comp.sources.misc
  2. subject: v07i120: cal(1) - print calendar
  3. from: allbery@uunet.UU.NET (Brandon S. Allbery - comp.sources.misc)
  4. Reply-To: vojta%math.Berkeley.EDU@ucbvax.Berkeley.EDU
  5.  
  6. Posting-number: Volume 7, Issue 120
  7. Submitted-by: vojta%math.Berkeley.EDU@ucbvax.Berkeley.EDU
  8. Archive-name: cal
  9.  
  10. Here's a version of cal(1) which I got from comp.sources.amiga.  I've spiffed
  11. it up to work under BSD Un*x and Turbo C, and added a man page.  Enjoy.
  12.  
  13. --Paul Vojta, vojta@math.berkeley.edu
  14.  
  15. #! /bin/sh
  16. # This is a shell archive.  Remove anything before this line, then unpack
  17. # it by saving it into a file and typing "sh file".  To overwrite existing
  18. # files, type "sh file -c".  You can also feed this as standard input via
  19. # unshar, or by typing "sh <file", e.g..  If this archive is complete, you
  20. # will see the following message at the end:
  21. #        "End of shell archive."
  22. # Contents:  cal.1 cal.c
  23. # Wrapped by vojta@maypo on Sat Aug  5 18:02:33 1989
  24. PATH=/bin:/usr/bin:/usr/ucb ; export PATH
  25. if test -f 'cal.1' -a "${1}" != "-c" ; then 
  26.   echo shar: Will not clobber existing file \"'cal.1'\"
  27. else
  28. echo shar: Extracting \"'cal.1'\" \(491 characters\)
  29. sed "s/^X//" >'cal.1' <<'END_OF_FILE'
  30. X.TH CAL 1 "5 Aug 1989" COMP.SOURCES.AMIGA
  31. X.SH NAME
  32. Xcal \- print calendar
  33. X.SH SYNOPSIS
  34. X.B cal
  35. X[[month] year]
  36. X.SH DESCRIPTION
  37. X.I Cal
  38. Xis a program which prints out a calendar either for a given month or for a
  39. Xgiven year.  By default, it prints a calendar for the current month.  It
  40. Xcorrectly handles the transition from the Julian to Gregorian calendars
  41. Xin September 1752 (at least in England and colonies).
  42. X.SH BUGS
  43. XNote that `cal 89' refers to 89 A. D., not to 1989.
  44. X.SH AUTHOR
  45. XGary L. Brant
  46. END_OF_FILE
  47. if test 491 -ne `wc -c <'cal.1'`; then
  48.     echo shar: \"'cal.1'\" unpacked with wrong size!
  49. fi
  50. # end of 'cal.1'
  51. fi
  52. if test -f 'cal.c' -a "${1}" != "-c" ; then 
  53.   echo shar: Will not clobber existing file \"'cal.c'\"
  54. else
  55. echo shar: Extracting \"'cal.c'\" \(5158 characters\)
  56. sed "s/^X//" >'cal.c' <<'END_OF_FILE'
  57. X/* cal.c - print calendar for one month or one year
  58. X *
  59. X * cal [[month] year]
  60. X * 
  61. X * cal (C) 1988 by Gary L. Brant
  62. X */
  63. X
  64. X#include <stdio.h>
  65. X#include <time.h>
  66. X#include <ctype.h>
  67. X#include <string.h>
  68. X#include <sys/types.h>
  69. X
  70. X#define    blank(addr, len)    (void) memset(addr, ' ', len)
  71. X
  72. X#define DPY    365L    /* days per year */
  73. X#define FUDGE1    1    /* needed to make day of week come out right */
  74. X#define FUDGE2    6    /* for old style (Julian) calendar */
  75. X#define    LINEWID    71    /* width of array line[] */
  76. X
  77. Xint days[12] = {
  78. X    31,  28,  31,  30,    31,  30,  31,  31,  30,  31,  30,  31
  79. X};
  80. Xint mdays[13] = {
  81. X     0,  31,  59,  90, 120, 151, 181, 212, 243, 273, 304, 334, 365
  82. X};
  83. Xchar *months[12] = {
  84. X   "January ", "February ", "March ",     "April ",   "May ",      "June ",
  85. X   "July "   , "August " , "September ", "October ", "November ", "December "
  86. X};
  87. Xchar monthline[] = "\t ---\t\t\t---\t\t       ---";
  88. Xchar *monthpos[3] = {monthline+2, monthline+8, monthline+20};
  89. Xchar dayline[] = " S  M Tu  W Th  F  S";
  90. Xchar line[7][LINEWID];        /* line buffer */
  91. Xint multi = 0;
  92. X
  93. X
  94. Xmain(argc, argv)
  95. Xint argc;
  96. Xchar *argv[];
  97. X{
  98. X   int i, k, m, y;
  99. X   time_t t;
  100. X   struct tm *lcl_tim;
  101. X
  102. X   t = time((time_t *) 0);
  103. X   lcl_tim = localtime(&t);
  104. X   y = lcl_tim->tm_year + 1900;
  105. X   m = lcl_tim->tm_mon + 1;
  106. X   if (argc == 1) {
  107. X      fixtab (y);
  108. X      printmonth (m, y);
  109. X      exit (0);
  110. X   }
  111. X
  112. X   if ((k = atoi (argv[1])) == 0) {
  113. X      m = 0;
  114. X      for (i = 0; i < 12; i++)
  115. X     if (cmpmonth (argv[1], months[i]) == 0) {
  116. X        m = i + 1;
  117. X        break;
  118. X     }
  119. X      if (m == 0) {
  120. X     badarg (argv[1]);
  121. X      }
  122. X   }
  123. X
  124. X   if (argc == 2) {
  125. X      if (k == 0) {
  126. X     fixtab (y);
  127. X     printmonth (m, y);
  128. X      } else {
  129. X     multi = 1;
  130. X     fixtab (k);
  131. X     fputs("\n\n\n\t\t\t\t", stdout);
  132. X     putd(k);        /* put year */
  133. X     putchar('\n');
  134. X     for (m = 1; m < 13; m++)
  135. X        printmonth (m, k);
  136. X     puts("\n\n");
  137. X      }
  138. X      exit (0);
  139. X   }
  140. X
  141. X   if (k > 0 && k < 13)
  142. X      m = k;
  143. X   else if (m == 0 || k != 0) {
  144. X      badarg (argv[1]);
  145. X   }
  146. X
  147. X   if (argc == 3) {
  148. X      if ((y = atoi (argv[2])) == 0) {
  149. X     badarg (argv[2]);
  150. X      }
  151. X   }
  152. X   fixtab (y);
  153. X   printmonth (m, y);
  154. X}
  155. X
  156. X
  157. X/* printmonth () - either prints an entire month at a time or multiplexes
  158. X * a month into a buffer, dumping the buffer after the third call.
  159. X */
  160. Xprintmonth (m, y)
  161. Xregister int m;
  162. Xint y;
  163. X{
  164. X   register int first, last;
  165. X   register int index, p = 0;
  166. X   register char *ll;
  167. X   static int q = 0;
  168. X   int l;
  169. X
  170. X   --m;
  171. X   if (multi) {
  172. X      q++;
  173. X      if (q > 3)
  174. X     q = 1;
  175. X      p = 23 * (q - 1);        /* character position of line in buffer */
  176. X      (void) memcpy(monthpos[q-1], months[m], 3);    /* copy month name */
  177. X      if (q == 3) {
  178. X     puts(monthline);
  179. X     for (index = 0; index < 2; ++index) {
  180. X        fputs(dayline, stdout);
  181. X        fputs("   ", stdout);
  182. X     }
  183. X     puts(dayline);
  184. X      }
  185. X      else
  186. X     blank(line[0]+p+12, 11);
  187. X   } else {
  188. X      q = 1;
  189. X      fputs("   ", stdout);
  190. X      fputs(months[m], stdout);            /* put month name */
  191. X      putd(y);                    /* put year */
  192. X      puts(dayline);
  193. X   }
  194. X
  195. X   l = 1;
  196. X   if (p == 0) blank(line[1], 6*LINEWID);
  197. X
  198. X   if (y == 1752 && m == 8) {    /* special case Sep. 1752 */
  199. X      line[1][p + 7] = '1';
  200. X      line[1][p + 10] = '2';
  201. X      first = 14;
  202. X      last = 16;
  203. X      index = 12;
  204. X   }
  205. X   else {
  206. X      int dow;            /* day of week for first day of month */
  207. X
  208. X      first = 1;
  209. X      dow = weekday (m, y);
  210. X      last = 7 - dow;
  211. X      index = 3 * dow;
  212. X   }
  213. X
  214. X   for (; l < 7; ++l) {    /* loop thru month one week per line */
  215. X      ll = line[l] + p;
  216. X      while (first <= last) {    /* for each day in week encode day of month */
  217. X     if (first >= 10)
  218. X        ll[index] = '0' + first / 10;
  219. X     ll[index+1] = '0' + first % 10;
  220. X     index += 3;
  221. X     ++first;
  222. X      }
  223. X      if (!multi || q == 3) {
  224. X     index += p - 2;
  225. X     if (index < 0) index = 0;
  226. X     ll -= p;
  227. X     while (index >= 0 && ll[index] == ' ')
  228. X        --index;
  229. X     ll[index+1] = '\0';
  230. X     puts(ll);
  231. X      }
  232. X      last = (last + 7) > days[m] ? days[m] : last + 7;
  233. X      index = 0;
  234. X   }
  235. X
  236. X}
  237. X
  238. X
  239. X/* putd - put year to standard output.
  240. X */
  241. Xputd (n)
  242. Xregister int n;
  243. X{
  244. X   char str[5];
  245. X   register char *p = str+4;
  246. X
  247. X   *p = '\0';
  248. X   do {
  249. X      --p;
  250. X      *p = '0' + n % 10;
  251. X      n = n / 10;
  252. X   }
  253. X   while (n);
  254. X   puts(p);
  255. X}
  256. X
  257. X
  258. X/* fixtab - correct for leapyears.
  259. X */
  260. Xfixtab (y)
  261. Xregister int y;
  262. X{
  263. X   register int i;
  264. X
  265. X   if ((y % 4) == 0) {
  266. X      if (((y % 100) != 0) || ((y % 400) == 0) || (y < 1753)) {
  267. X     days[1] = 29;
  268. X     for (i = 2; i < 13; i++)
  269. X        mdays[i]++;
  270. X      }
  271. X   }
  272. X}
  273. X
  274. X
  275. X/* weekday - return day-of-week for first day of month.
  276. X */
  277. Xweekday (m, y)
  278. Xregister int m, y;
  279. X{
  280. X   --y;
  281. X   if (y > 1752-1 || (y == 1752-1 && m > 8))
  282. X      return (mdays[m] + y + y / 4 - y / 100 + y / 400 + FUDGE1) % 7;
  283. X   else
  284. X      return (mdays[m] + y + y / 4               + FUDGE2) % 7;
  285. X}
  286. X
  287. X
  288. X
  289. Xbadarg (string)
  290. Xchar string[];
  291. X{
  292. X   fputs(string, stderr);
  293. X   fputs(" bad argument\n", stderr);
  294. X   exit (10);
  295. X}
  296. X
  297. X
  298. X/* cmpmonth () - compare month argument entered by user with month name.
  299. X * The comparison will be made case insensitive.
  300. X */
  301. Xcmpmonth (str1, str2)
  302. Xregister char str1[], str2[];
  303. X{
  304. X   register int j;
  305. X
  306. X   if ((j = (toupper(str1[0])-str2[0])) != 0)
  307. X      return (j);
  308. X   else if ((j = tolower(str1[1])-str2[1]) != 0)
  309. X      return (j);
  310. X   else
  311. X      return (tolower(str1[2])-str2[2]);
  312. X}
  313. END_OF_FILE
  314. if test 5158 -ne `wc -c <'cal.c'`; then
  315.     echo shar: \"'cal.c'\" unpacked with wrong size!
  316. fi
  317. # end of 'cal.c'
  318. fi
  319. echo shar: End of shell archive.
  320. exit 0
  321.  
  322.